<?php

namespace App\Service\Kms\Common;

use App\Http\Resources\Kms\User\UserResource;
use App\Models\Kms\Fs\FsDepartmentsModel;
use App\Models\Kms\User\KmsUser;
use App\Models\Kms\User\KmsUserConfigModel;
use App\Service\Kms\KmsBaseService;
use Illuminate\Support\Facades\Cache;

class FeishuService extends KmsBaseService
{
    /**
     * @return mixed
     */
    public static function getDepartments()
    {
        return Cache::store("redis")->remember("feishu:getDepartments", 60 * 60, function () {
            $fsDepartments = FsDepartmentsModel::query()->with("userRel")->select([
                "openDepartmentId",
                "parentDepartmentId",
                "name",
                "memberCount",
                "order"
            ])->get()->keyBy("openDepartmentId")->toArray();

            $tree = [];
            foreach ($fsDepartments as &$department) {
                if (!empty($department["parentDepartmentId"])) {
                    $fsDepartments[$department["parentDepartmentId"]]["child"][] = &$department;
                } else {
                    $tree[] = &$department;
                }
            }
            unset($fsDepartments);

            $linkDepartment       = [];
            $getRowDepartmentFunc = function (
                array $department,
                array $container,
                \Closure $func,
                array &$linkDepartment
            ) {
                collect($department)->each(function ($department) use ($container, $func, &$linkDepartment) {
                    array_push($container, $department["openDepartmentId"]);
                    if (array_key_exists("child", $department)) {
                        $func($department["child"], $container, $func, $linkDepartment);
                    } else {
                        $key                  = end($container);
                        $linkDepartment[$key] = $container;
                    }
                });
            };

            $getRowDepartmentFunc($tree, [], $getRowDepartmentFunc, $linkDepartment);

            return [
                "treeDepartments"  => $tree,
                "levelDepartments" => $linkDepartment
            ];
        });
    }

    /**
     * @return array
     */
    public static function departments(): array
    {
        return [
            "list"  => self::getDepartments()["treeDepartments"],
            "level" => self::getDepartments()["levelDepartments"]
        ];
    }

    /**
     * @param int $pageSize
     * @param int $pageNum
     * @param string $departmentId
     * @param string $jobTitle
     * @param string $name
     * @param int|null $fieldSwitch
     * @param int $selection
     * @return array[]
     */
    public static function user(
        int $pageSize = 10,
        int $pageNum = 1,
        string $departmentId = "",
        string $jobTitle = "",
        string $name = "",
        int $fieldSwitch = null,
        int $selection = 0
    ): array {
        $userList = KmsUser::query()->when($departmentId, function ($query) use ($departmentId) {
            return $query->where("rootDepartmentId", $departmentId);
        })->when($jobTitle, function ($query) use ($jobTitle) {
            return $query->where("jobTitle", $jobTitle);
        })->when($name, function ($query) use ($name) {
            $query->where(function ($query) use ($name) {
                $query->where("name", "like", "%$name%")->orWhere("nickname", "like", "%$name%");
            });
        })->when(!is_null($fieldSwitch), function ($query) use ($fieldSwitch) {
            $kmsUserConfig = KmsUserConfigModel::query()
                                               ->where("fieldSwitch", KmsUserConfigModel::FIELD_SWITCH_ON)
                                               ->get();
            if ($fieldSwitch) {
                $query->whereIn("rmsUserId", $kmsUserConfig->pluck("userId")->toArray());
            } else {
                $query->whereNotIn("rmsUserId", $kmsUserConfig->pluck("userId")->toArray());
            }
        })->where("isExited", 0)->where("rmsUserId", ">", 0)
                           ->groupBy("rmsUserId")->when($selection, function ($query) {
                return $query->select(["rmsUserId", "nickname", "name"])->get();
            }, function ($query) use ($pageNum, $pageSize) {
                return $query->with(
                    ["userConfigRel", "lastLoginHistory"]
                )->paginate($pageSize, ['*'], 'pageNum', $pageNum);
            });

        if ($selection) {
            return ["list" => $userList->toArray()];
        } else {
            return [
                "userList" => [
                    "total"    => $userList->total(),
                    "pageNum"  => $userList->currentPage(),
                    "pageSize" => $pageSize,
                    "list"     => UserResource::collection($userList->items())
                ]
            ];
        }
    }

    /**
     * @return array
     */
    public static function selection(): array
    {
        return [
            "rootDepartmentSelection" => FsDepartmentsModel::query()
                                                           ->where("parentDepartmentId", "0")
                                                           ->orderBy("order")
                                                           ->select([
                                                               "openDepartmentId as key",
                                                               "name as value"
                                                           ])->get()->toArray(),
            "jobTitleSelection"       => KmsUser::query()
                                                ->where("rmsUserId", ">", 0)
                                                ->where("jobTitle", "<>", "")
                                                ->groupBy("jobTitle")
                                                ->select(["jobTitle as key", "jobTitle as value"])
                                                ->get()->toArray(),
        ];
    }

}
